﻿package core.drawing
{
    import __AS3__.vec.*;
    import core.enum.*;
    import flash.events.*;

    final public class SmudgeTool extends ShapeTool
    {
        var pattern:Vector.<uint>;
        var px:uint;
        var color:uint;
        var f:Number;
        var tf:Number;
        var n:int;
        var cx:int;
        var cy:int;
        var sx:int;
        var sy:int;
        var alpha:int;
        var a:int;
        var r:int;
        var g:int;
        var b:int;
        var ta:int;
        var tr:int;
        var tg:int;
        var tb:int;

        public function SmudgeTool(param1:Tuyitu)
        {
            super(param1, ToolType.Smudge);
            return;
        }// end function

        override public function MouseDown(event:MouseEvent) : void
        {
            if (!type.attitude.locked)
            {
                this.UpdateReferences();
                this.Prepare(Action.SmudgeTool, layer.activeBitmap);
                this.pattern = new Vector.<uint>(shape.data.length, true);
                if (!event.shiftKey)
                {
                    var _loc_2:int = -1;
                    y = -1;
                    x = _loc_2;
                }
                this.SetPattern();
            }
            return;
        }// end function

        override public function MouseDrag(event:MouseEvent) : void
        {
            if (target != null)
            {
                p = canvas.GetOffsetMousePosition(offset);
                target.lock();
                if (x == -1)
                {
                    x = p.x;
                    y = p.y;
                    this.DrawShape(x, y);
                }
                if (p.x != x || p.y != y)
                {
                    dx = p.x - x;
                    dy = p.y - y;
                    xinc = dx > 0 ? (1) : (-1);
                    yinc = dy > 0 ? (1) : (-1);
                    dx = dx < 0 ? (-dx) : (dx);
                    dy = dy < 0 ? (-dy) : (dy);
                    if (dx > dy)
                    {
                        cumul = dx * 0.5;
                        i = 1;
                        while (i <= dx)
                        {
                            
                            x = x + xinc;
                            cumul = cumul + dy;
                            if (cumul >= dx)
                            {
                                cumul = cumul - dx;
                                y = y + yinc;
                            }
                            this.DrawShape(x, y);
                            var _loc_3:* = i + 1;
                            i = _loc_3;
                        }
                    }
                    else
                    {
                        cumul = dy * 0.5;
                        i = 1;
                        while (i <= dy)
                        {
                            
                            y = y + yinc;
                            cumul = cumul + dx;
                            if (cumul >= dy)
                            {
                                cumul = cumul - dy;
                                x = x + xinc;
                            }
                            this.DrawShape(x, y);
                            var _loc_3:* = i + 1;
                            i = _loc_3;
                        }
                    }
                }
                target.unlock();
            }
            return;
        }// end function

        override public function DrawShape(Action:int, Action:int) : void
        {
            this.n = 0;
            this.sy = Action - int(shape.height * 0.5);
            this.cy = this.sy + shape.height;
            while (this.sy < this.cy)
            {
                
                this.sx = Action - int(shape.width * 0.5);
                this.cx = this.sx + shape.width;
                while (this.sx < this.cx)
                {
                    
                    this.alpha = shape.data[this.n] * options.strength;
                    if (this.alpha > 0)
                    {
                        if (selection == null || selection.IsSelected(this.sx + offset.x, this.sy + offset.y))
                        {
                            this.color = this.pattern[this.n];
                            this.ta = this.alpha;
                            this.tr = this.color >>> 16 & 255;
                            this.tg = this.color >>> 8 & 255;
                            this.tb = this.color & 255;
                            this.px = target.getPixel32(this.sx, this.sy);
                            this.a = this.px >>> 24 & 255;
                            this.r = this.px >>> 16 & 255;
                            this.g = this.px >>> 8 & 255;
                            this.b = this.px & 255;
                            if (this.a == 255 || this.a != 0)
                            {
                                this.ta = this.a + this.alpha > 255 ? (255) : (this.a + this.alpha);
                                this.tr = this.tr * (this.alpha / 255) + this.r * ((255 - this.alpha) / 255);
                                this.tg = this.tg * (this.alpha / 255) + this.g * ((255 - this.alpha) / 255);
                                this.tb = this.tb * (this.alpha / 255) + this.b * ((255 - this.alpha) / 255);
                            }
                            target.setPixel32(this.sx, this.sy, this.ta << 24 | this.tr << 16 | this.tg << 8 | this.tb);
                            this.a = this.color >>> 24 & 255;
                            this.r = this.color >>> 16 & 255;
                            this.g = this.color >>> 8 & 255;
                            this.b = this.color & 255;
                            this.ta = this.a + this.ta;
                            this.tr = Math.round(this.r * options.strength + this.tr * (1 - options.strength));
                            this.tg = Math.round(this.g * options.strength + this.tg * (1 - options.strength));
                            this.tb = Math.round(this.b * options.strength + this.tb * (1 - options.strength));
                            if (this.ta > 255)
                            {
                                this.ta = 255;
                            }
                            if (this.tr > 255)
                            {
                                this.tr = 255;
                            }
                            if (this.tg > 255)
                            {
                                this.tg = 255;
                            }
                            if (this.tb > 255)
                            {
                                this.tb = 255;
                            }
                            this.pattern[this.n] = this.ta << 24 | this.tr << 16 | this.tg << 8 | this.tb;
                        }
                        else
                        {
                            this.pattern[this.n] = this.CombinePixels(this.color, target.getPixel32(this.sx, this.sy), options.strength);
                        }
                    }
                    var _loc_3:String = this;
                    var _loc_4:* = this.n + 1;
                    _loc_3.n = _loc_4;
                    var _loc_3:String = this;
                    var _loc_4:* = this.sx + 1;
                    _loc_3.sx = _loc_4;
                }
                var _loc_3:String = this;
                var _loc_4:* = this.sy + 1;
                _loc_3.sy = _loc_4;
            }
            return;
        }// end function

        public function CombinePixels(core.drawing:uint, core.drawing:uint, core.drawing:Number) : uint
        {
            if (core.drawing == 1)
            {
                return core.drawing;
            }
            if (core.drawing == core.drawing)
            {
                return core.drawing;
            }
            this.a = core.drawing >>> 24 & 255;
            this.r = core.drawing >>> 16 & 255;
            this.g = core.drawing >>> 8 & 255;
            this.b = core.drawing & 255;
            this.ta = core.drawing >>> 24 & 255;
            this.tr = core.drawing >>> 16 & 255;
            this.tg = core.drawing >>> 8 & 255;
            this.tb = core.drawing & 255;
            this.a = this.a + this.ta;
            if (this.ta > 0)
            {
                this.r = Math.round(this.r * core.drawing + this.tr * (1 - core.drawing) + 1);
                this.g = Math.round(this.g * core.drawing + this.tg * (1 - core.drawing) + 1);
                this.b = Math.round(this.b * core.drawing + this.tb * (1 - core.drawing) + 1);
            }
            if (this.a > 255)
            {
                this.a = 255;
            }
            if (this.r > 255)
            {
                this.r = 255;
            }
            if (this.g > 255)
            {
                this.g = 255;
            }
            if (this.b > 255)
            {
                this.b = 255;
            }
            return (this.a << 24) + (this.r << 16) + (this.g << 8) + this.b;
        }// end function

        public function SetPattern() : void
        {
            var _loc_1:* = undefined;
            if (target != null)
            {
                p = canvas.GetOffsetMousePosition(offset);
                this.n = -1;
                this.sy = p.y - int((shape.height - 1) * 0.5);
                this.cy = this.sy + shape.height;
                while (this.sy < this.cy)
                {
                    
                    this.sx = p.x - int((shape.width - 1) * 0.5);
                    this.cx = this.sx + shape.width;
                    while (this.sx < this.cx)
                    {
                        
                        var _loc_2:String = this;
                        _loc_2.n = this.n + 1;
                        _loc_1 = this.n + 1;
                        this.pattern[_loc_1] = target.getPixel32(this.sx, this.sy);
                        var _loc_2:String = this;
                        var _loc_3:* = this.sx + 1;
                        _loc_2.sx = _loc_3;
                    }
                    var _loc_2:String = this;
                    var _loc_3:* = this.sy + 1;
                    _loc_2.sy = _loc_3;
                }
            }
            return;
        }// end function

    }
}
